package cn.imvc.app.models;


import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
import java.util.List;

import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.stereotype.Service;

import cn.imvc.app.domains.FundFlowType;
import cn.imvc.app.domains.OrderState;
import cn.imvc.app.domains.OrderType;
import cn.imvc.app.entities.Dealer;
import cn.imvc.app.entities.DealerApply;
import cn.imvc.app.entities.DealerLevel;
import cn.imvc.app.entities.Member;
import cn.imvc.app.repositories.DealerApplyRepository;
import cn.imvc.data.domain.ViewRequest;
import cn.imvc.util.RandomId;

@Service
public class DealerApplyModelImpl implements DealerApplyModel{
	
	@Autowired
	private DealerApplyRepository dealerApplyRepository;
	
	@Autowired
	private DealerLevelModel dealerLevelModel;
	
	@Autowired
	private DealerModel dealerModel;
	
	@Autowired
	private FundFlowModel fundFlowModel;
	
	@Autowired
	private DomainModel domainModel;
	
	@Autowired
	private CommissionModel commissionModel;
	
	
	
	public DealerApply get(int id){
		return dealerApplyRepository.findOne(id);
	}
	
	
	public Page<DealerApply> find(ViewRequest viewRequest) {
		return (Page<DealerApply>) dealerApplyRepository.findAll();
	}

	public DealerApply save(DealerApply dealerApply) {
		
		DealerApply dealerApply2 = dealerApplyRepository.saveAndFlush(dealerApply);
		
		
		return dealerApply2;
	}
	public DealerApply update(DealerApply newDealerApply) {
		DealerApply loadDealerApply=get(newDealerApply.getId());
		BeanUtils.copyProperties(newDealerApply, loadDealerApply, new String[]{"id"});
		
		return dealerApplyRepository.saveAndFlush(loadDealerApply);
	}
	public void delete(int id) {
		dealerApplyRepository.delete(id);
		
	}
	public void deleteBatch(int[] ids) {

		for (int id : ids) {
			delete(id);
		}
		
	}
	
	public DealerApply findByCode(String code){
		return dealerApplyRepository.findByCode(code);
	}
	
	public List<DealerApply> checkUnFinishedOrder(int memberId){
		
		Collection<Byte> states = new ArrayList<Byte>();
		states.add(OrderState.Create.getValue());
		states.add(OrderState.Payment.getValue());
		
		return dealerApplyRepository.findByMemberIdAndStateIn(memberId, states);
		
	}
	
	//保存分销商升级订单
	public DealerApply saveDealerApplyOrder(int levelId,Member member){
		
		DealerLevel dealerLevel=dealerLevelModel.get(levelId);
		Dealer dealer=member.getDealer();
		
		DealerApply dealerApply=new DealerApply();
		dealerApply.setType((byte)0);
		dealerApply.setCreatedAt(new Date());	
		dealerApply.setUpdatedAt(new Date());
		dealerApply.setDealerLevel(dealerLevel);
		dealerApply.setState(OrderState.Create.getValue());
		dealerApply.setMember(member);		
		dealerApply.setCode(OrderType.Upgrade.getValue()+RandomId.randomId(new Date().getTime()));
		dealerApply.setJoinMoney(dealerLevel.getJoinMoney()-(dealer==null?0:dealer.getDealerLevel().getJoinMoney()));
		dealerApply.setJoinPoint(dealerLevel.getJoinPoint()-(dealer==null?0:dealer.getDealerLevel().getJoinPoint()));
		dealerApply.setDomain(dealer==null?domainModel.findBymemberId(member.getId()).getDomain():dealer.getDomain());
		return save(dealerApply);
	}
	//分销商升级订单完成
	public void finishPay(String code,String payCode,Date payTime){
		//改变订单状态和付款时间
		DealerApply dealerApply=findByCode(code);
		if(dealerApply.getState()!=OrderState.Payment.getValue()){
			return;
		}
		dealerApply.setState(OrderState.PaySuccess.getValue());
		dealerApply.setPayCode(payCode);
		dealerApply.setPayTime(payTime);
		dealerApply.setUpdatedAt(new Date());
		save(dealerApply);
		
		//如果第一次升级，创建dealer对象，否则更新dealer对象
		Member member=dealerApply.getMember();
		Dealer dealer=member.getDealer();
		if (dealer==null){
			dealer=new Dealer();
			dealer.setMember(member);
			dealer.setName(member.getName());
			dealer.setCreatedAt(new Date());
			dealer.setUpdatedAt(new Date());
			dealer.setDomain(domainModel.findBymemberId(member.getId()).getDomain());
		}
		dealer.setDealerLevel(dealerApply.getDealerLevel());
		dealerModel.save(dealer);
		fundFlowModel.addFundFlow(member, -dealerApply.getJoinMoney(), code, FundFlowType.Upgrade.getValue(),member);
		commissionModel.addCommission(member, (byte)2, dealerApply.getId());
		
	}


}
